﻿using SimpleCrawler.DAL;
using SimpleCrawler.DependencyInjection;
using SimpleCrawler.Entity;
using System;
using System.Collections.Generic;
using System.Text.RegularExpressions;
using System.Threading.Tasks;
using Microsoft.Extensions.DependencyInjection;
using System.Threading;

namespace SimpleCrawler.Crawler
{
    public class QiHu360WenDaCrawler : CrawlerBase
    {    
        //private ILog logger;    
        CrawlerDAL dal;
        public QiHu360WenDaCrawler():base(1005,"360问答") {
            //logger = LoggerManager.GetLogger(GetType());
            dal = AppServiceProvider.ServiceProvider.GetService<CrawlerDAL>();
        }

        public override void GetStartedPageUrl()
        {        
            RequestUrl = $"http://wenda.so.com/search/?adv_t=m&q={System.Web.HttpUtility.UrlEncode(CrawlerTask.KeyWord)}&filt=20&pn=0";
        }
        public override void GetNextPageUrl(int page)
        {
            RequestUrl = $"http://wenda.so.com/search/?adv_t=m&q={System.Web.HttpUtility.UrlEncode(CrawlerTask.KeyWord)}&filt=20&pn={page-1}";
        }


        public async override Task<int> GetResultContent(string html)
        {
            Match table = Regex.Match(html, @"<ul class=""qa-list"">[\s\S]*?<div class=""to_haosou"">");
            MatchCollection trlist = Regex.Matches(table.ToString(), @"<li class=""item"">[\s\S]*?</li>");
            Regex realUrlReg = new Regex(@"<h3><a[\s\S]*?href=""([\s\S]*?)""");

            Regex quetionReg = new Regex(@"<div class=""mod-q js-form""[\s\S]*?title js-ask-title"">([\s\S]*?)</h2>[\s\S]*?<span>被浏览(\d*)次[\s\S]*?<span>(\d{4}-\d{2}-\d{2}|\d{4}.\d{2}.\d{2})</span>");
            Regex bestAnswer = new Regex(@"<div class=""top-line"">[\s\S]*?(\d{4}-\d{2}-\d{2}|\d{4}.\d{2}.\d{2})</span>[\s\S]*?class=""resolved-cnt"">([\s\S]*?)"
+@"</div><div class=""mod-added-qa js-[\s\S]*?js-laud good[\s\S]*?<span>(\d*)</span>[\s\S]*?js-laud bad[\s\S]*?<span>(\d*)</span>");

            Regex otherAnswers = new Regex(@"<div class=""answers"">[\s\S]*?class=""mod-related_search""");
            Regex otherAnswer = new Regex(@"<li[\s\S]*?class=""time"" >(\d{4}-\d{2}-\d{2}|\d{4}.\d{2}.\d{2})</span>[\s\S]*?class=""other-ans-cnt"">([\s\S]*?)</div>[\s\S]*?<i>很给力</i><span>(\d*)</span>[\s\S]*?</li>");

            List<WD_Question> questions = new List<WD_Question>();
            if (trlist.Count > 0)
            {
                foreach (var tr in trlist)
                {
                    Match MrealUrl = realUrlReg.Match(tr.ToString());
                    if (MrealUrl.Success)
                    {
                        WD_Question question = new WD_Question();
                        string url = "https://wenda.so.com" + MrealUrl.Groups[1].ToString().Trim();
                        //url过滤
                        if (Filter != null && Filter.Contains(url))
                        {
                            Logger.Error($"已过滤的问答,link=>{url}");
                            FilterCount++;
                            continue;
                        }
                        Filter.Add(url);
                        //
                        string detailHtml = await SendRequestByGet(url);
                        Thread.Sleep(10 * 1000);
                        Match Mquestion = quetionReg.Match(detailHtml);
                        if (Mquestion.Success)
                        {
                            try
                            {
                                question.SourceSite = this.CrawlerID;
                                question.KeyWord = this.CrawlerTask.KeyWord;
                                question.SourceUrl = url;
                                question.Question =Mquestion.Groups[1].ToString();
                                question.ShowCount = int.Parse(Mquestion.Groups[2].ToString());
                                question.CreateTime = DateTime.Parse(Mquestion.Groups[3].ToString());
                            }
                            catch (Exception ex)
                            {
                                Logger.Error($"问题匹配出错,link=>{url} {ex.ToString()}");
                            }
                            if (string.IsNullOrEmpty(question.Question) || question.CreateTime == null)
                                continue;
                        }
                        else
                        {
                            Logger.Error($"问题匹配出错,link=>{url}");
                            continue;
                        }
                        question.Answers = new List<WD_Answer>();
                        Match MbestAnswer = bestAnswer.Match(detailHtml);
                        if (MbestAnswer.Success)
                        {
                            WD_Answer answer = new WD_Answer();
                            try
                            {
                                answer.IsAdopt = 1;
                                answer.Answer = MbestAnswer.Groups[2].ToString();
                                answer.AnswerLen = answer.Answer.Length;
                                answer.CreateDate = DateTime.Parse(MbestAnswer.Groups[1].ToString());
                                answer.ZanCount = int.Parse(MbestAnswer.Groups[3].ToString());
                                answer.CaiCount = int.Parse(MbestAnswer.Groups[4].ToString());
                            }
                            catch (Exception ex)
                            {
                                Logger.Error($"最佳答案匹配出错,link=>{url} {ex.ToString()}");
                            }
                            if (!string.IsNullOrEmpty(answer.Answer))
                            {
                                question.Answers.Add(answer);
                            }
                        }

                        MatchCollection MotherAnswers = otherAnswer.Matches(otherAnswers.Match(detailHtml).ToString());
                        foreach (Match item in MotherAnswers)
                        {
                            WD_Answer answer = new WD_Answer();
                            try
                            {
                                answer.Answer = item.Groups[2].ToString();
                                answer.AnswerLen = answer.Answer.Length;
                                answer.CreateDate = DateTime.Parse(item.Groups[1].ToString());
                                answer.ZanCount = int.Parse(item.Groups[3].ToString());
                            }
                            catch (Exception ex)
                            {
                                Logger.Error($"其他答案匹配出错,link=>{url} {ex.ToString()}");
                            }
                            if (!string.IsNullOrEmpty(answer.Answer))
                            {
                                question.Answers.Add(answer);
                            }
                        }
                        questions.Add(question);
                        if (question.Answers.Count == 0)
                            Logger.Error($"未匹配到答案,link=>{url}");
                    }
                    else
                    {
                        continue;
                    }
                }
            }

            if (FilterCount > 0 && trlist.Count == FilterCount)
            {
                FilterCount = 0;
                return -1;
            }
            FilterCount = 0;

            if (questions.Count > 0)
            {
                var result = await SaveToDB(questions);
                Match next = Regex.Match(html, @"<p class=""pages"">[\s\S]*?>下一页</a></p>");
                if (questions.Count > 0 && next.Success)
                {
                    CrawlerTask.EndPage = CrawlerTask.StartPage + 1;
                }
                if (!string.IsNullOrEmpty(result.Content))
                {
                    Logger.Error(result.Content);
                }
                return result.Count;
            }
            return 0;

        }

        protected async Task<(int Count, string Content)> SaveToDB(List<WD_Question> list)
        {
            return await dal.AddQuestions(list).ConfigureAwait(continueOnCapturedContext: false);
        }
    }
}
